#ifndef __ARC_MACRO_H__
#define __ARC_MACRO_H__
/*--------------------2012-02-02 20:24:55-------------------------------------------------*/
#define MakeGDTDescriptor(gdt,base,limit,attribute)                                      \
         { (gdt).limit0             =   (U2B)(0xFFFF & (((U4B)limit)>>12));              \
          (gdt).base0              =   (U2B)(0xFFFF & ((U4B)base));                      \
          (gdt).base1              =   (U1B)(0xFF   & (((U4B)base)>>16));                \
          (gdt).pdplstype0         =   (U1B)(0xFF   & (attribute));                      \
          (gdt).gdb0avllimit1      =   (U1B)(0xC0   | ((U1B)(((limit)>>28) & 0x0F)));    \
          (gdt).base2              =   (U1B)(0xFF   & (((U4B)base)>>24));} 

#define MakeGDTPtr(gdtptr,limit,base)                                                    \
        {  (gdtptr).limit0          =   (U2B)(0xFFFF & (limit));                         \
          (gdtptr).base0           =   (U2B)(0xFFFF & ((U4B)(base)) );                   \
          (gdtptr).base1           =   (U2B)(0xFFFF & (((U4B)(base))>>16)); }                 

#define MakeGateDescriptor(gate,offset,selector,attribute)                               \
        {  (gate).offset0           =   (U2B)(0xFFFF &((U4B) (offset)));                        \
          (gate).selector0         =   (U2B)(selector);                                  \
          (gate).three0paramcount0 =   (U1B)(0);                                         \
          (gate).pdplstype0        =   (U1B)(attribute);                                 \
          (gate).offset1           =   (U2B)(0xFFFF & (((U4B)(offset))>>16));}   
              
#define MakeIDTPtr(idtptr,limit,base)                                                    \
          {(idtptr).limit0          =   (U2B)(0xFFFF & (limit));                         \
          (idtptr).base0           =   (U2B)(0xFFFF & ((U4B)(base)) );                          \
          (idtptr).base1           =   (U2B)(0xFFFF & (((U4B)(base))>>16));}



#define GetEAX(label) \
       ({U4B __eax;__asm__("nop\n\t":"=a"(__eax):);__eax;})

#define GetEBX(label) \
       ({U4B __ebx;__asm__("nop\n\t":"=b"(__ebx):);__ebx;})

#define GetECX(label) \
       ({U4B __ecx;__asm__("nop\n\t":"=c"(__ecx):);__ecx;})

#define GetEDX(label) \
       ({U4B __edx;__asm__("nop\n\t":"=d"(__edx):);__edx;})

#define GetESI(label) \
       ({U4B __esi;__asm__("nop\n\t":"=S"(__esi):);__esi;})

#define GetEDI(label) \
       ({U4B __edi;__asm__("nop\n\t":"=D"(__edi):);__edi;})

#define GetESP(label) \
       ({U4B __esp;__asm__("movl %%esp,%%eax\n\t":"=a"(__esp):);__esp;})

#define GetCS(label) \
       ({U2B __cs;__asm__("movw %%cs,%%ax\n\tnop\n\t":"=a"(__cs):);__cs;})

#define GetDS(label) \
       ({U2B __ds;__asm__("movw %%ds,%%ax\n\tnop\n\t":"=a"(__ds):);__ds;})

#define GetES(label) \
       ({U2B __es;__asm__("movw %%es,%%ax\n\tnop\n\t":"=a"(__es):);__es;})

#define GetFS(label) \
       ({U2B __fs;__asm__("movw %%fs,%%ax\n\tnop\n\t":"=a"(__fs):);__fs;})

#define GetGS(label) \
       ({U2B __gs;__asm__("movw %%gs,%%ax\n\tnop\n\t":"=a"(__gs):);__gs;})

#define SetDS(__ds) \
       __asm__ __volatile__("movw %%ax,%%ds\n\t"::"a"(__ds));

#define SetES(__es) \
       __asm__ __volatile__("movw %%ax,%%es\n\t"::"a"(__es));

#define SetFS(__fs) \
       __asm__ __volatile__("movw %%ax,%%fs\n\t"::"a"(__fs));

#define SetGS(__gs) \
       __asm__ __volatile__("movw %%ax,%%gs\n\t"::"a"(__gs));
#define SetSS(__ss) \
       __asm__ __volatile__("movw %%ax,%%ss\n\t"::"a"(__ss));

#define SetESP(__esp) \
       __asm__ __volatile__("movl %%eax,%%esp\n\t"::"a"(__esp));

#define SetTR(__tr) \
       __asm__ __volatile__("ltr %%ax\n\t"::"a"(__tr));

#define GetCR3()    \
       ({U4B __cr3;__asm__ __volatile__("movl %%cr3,%%eax\n\t":"=a"(__cr3):);__cr3;})

#define GetCR0()      \
       ({U4B __cr0;__asm__ __volatile__("movl %%cr0,%%eax\n\t":"=a"(__cr0):);__cr0;})   

#define STI() \
       __asm__ __volatile__("sti\n\t"::);       

#endif
